<template>
	<view class="content">
		<!-- <view>{{scanResult.type}} </view>
		<view>{{scanResult.code}} </view>  
		<button @click="addScanCodeEvent">addScanCodeEvent</button>
		<button @click="removeScanCodeEvent">removeScanCodeEvent</button> -->
	</view>
</template>
<script>
	export default {
		data() {
			return {
				//hideKeyboardTimeoutId: null,
				getValueTimeoutId: null,
				//focusState: false,
				scanResult: {
					type: '',
					code: ''
				},
				//currentScan: '',
				//scanning: true,
				scanDate: 0,
				//timer: null, 
				keyCodeToStringMap: {
					"-8": "!",
					"62": " ",
					"-75": "\"",
					"-10": "#",
					"-11": "$",
					"-12": "%",
					"-14": "&",
					"75": "'",
					"-16": "(",
					"-7": ")",
					"-15": "*",
					"-70": "+",
					"55": ",",
					"69": "-",
					"56": ".",
					"76": "/",
					"7": "0",
					"8": "1",
					"9": "2",
					"10": "3",
					"11": "4",
					"12": "5",
					"13": "6",
					"14": "7",
					"15": "8",
					"16": "9",
					"-74": ":",
					"74": ";",
					"-55": "<",
					"70": "=",
					"-56": ">",
					"-76": "?",
					"-9": "@",
					"-29": "A",
					"-30": "B",
					"-31": "C",
					"-32": "D",
					"-33": "E",
					"-34": "F",
					"-35": "G",
					"-36": "H",
					"-37": "I",
					"-38": "J",
					"-39": "K",
					"-40": "L",
					"-41": "M",
					"-42": "N",
					"-43": "O",
					"-44": "P",
					"-45": "Q",
					"-46": "R",
					"-47": "S",
					"-48": "T",
					"-49": "U",
					"-50": "V",
					"-51": "W",
					"-52": "X",
					"-53": "Y",
					"-54": "Z",
					"71": "[",
					"73": "\\",
					"72": "]",
					"-13": "^",
					"-69": "_",
					"68": "`",
					"29": "a",
					"30": "b",
					"31": "c",
					"32": "d",
					"33": "e",
					"34": "f",
					"35": "g",
					"36": "h",
					"37": "i",
					"38": "j",
					"39": "k",
					"40": "l",
					"41": "m",
					"42": "n",
					"43": "o",
					"44": "p",
					"45": "q",
					"46": "r",
					"47": "s",
					"48": "t",
					"49": "u",
					"50": "v",
					"51": "w",
					"52": "x",
					"53": "y",
					"54": "z",
					"-71": "{",
					"-73": "|",
					"-72": "}",
					"-68": "~"
				},
				keyCodes: [],
				//ScanCodeOrIcStr: "",
				// ... 其他数据
				debounceTimeoutId: null,  // 防抖定时器ID
				lastEmittedCode: '',      // 上次发送的码值
				lastEmitTime: 0           // 上次发送的时间
			}
		},
		mounted() {
			console.log('加载监听读卡器扫码器方法')
			this.addScanCodeEvent()
		},
		onUnload() {
			console.log('卸载监听读卡器扫码器方法')
			this.removeScanCodeEvent();
		},
		// 在组件销毁时清除定时器
		beforeDestroy() {
			if (this.debounceTimeoutId) {
				clearTimeout(this.debounceTimeoutId);
			}
		},
		methods: {
			// 防抖方法
			debounceEmit(callback, delay = 300) {
				// 清除之前的定时器
				if (this.debounceTimeoutId) {
					clearTimeout(this.debounceTimeoutId);
				}

				// 设置新的定时器
				this.debounceTimeoutId = setTimeout(() => {
					callback();
				}, delay);
			},

			// 去除重复扫描数据的封装方法
			removeDuplicateData(data) {
				// 处理完全重复的情况，如 "abcabc" -> "abc"
				if (data.length % 2 === 0) {
					const halfLength = data.length / 2;
					const firstHalf = data.substring(0, halfLength);
					const secondHalf = data.substring(halfLength);

					// 如果前后两部分完全相同，则只返回其中一部分
					if (firstHalf === secondHalf) {
						return firstHalf;
					}
				}

				// 处理多重重复的情况，如 "abcabcabc" -> "abc"
				for (let i = 1; i <= Math.floor(data.length / 2); i++) {
					if (data.length % i === 0) {
						const pattern = data.substring(0, i);
						let isRepeated = true;

						for (let j = i; j < data.length; j += i) {
							if (data.substring(j, j + i) !== pattern) {
								isRepeated = false;
								break;
							}
						}

						if (isRepeated) {
							return pattern;
						}
					}
				}

				// 如果没有检测到重复，则返回原始数据
				return data;
			},
			ScanCodeCallback() {
				console.log("ScanCodeCallback")
				this.scanDate = 0;
				var keyCodes = [...this.keyCodes];
				this.keyCodes = [];
				if (keyCodes.length == 0) return;
				console.log("ScanCodeCallback", keyCodes)
				var scanData = '';
				try {
					for (var i = 0; i < keyCodes.length; i++) {
						var c = "";
						if (keyCodes[i] == 59) {
							i++;
							c = this.keyCodeToStringMap["-" + keyCodes[i].toString()];
						} else {
							c = this.keyCodeToStringMap[keyCodes[i].toString()];
						}
						if (c == undefined)
							break;
						scanData += c;
					}

				} catch (error) {
					console.log("ScanCodeCallback", error)
					//TODO handle the exception
				}

				// 使用去重方法处理扫描数据
				const uniqueScanData = this.removeDuplicateData(scanData);

				var len = scanData.length;
				if (len == 10 && !isNaN(Number(scanData))) {
					this.scanResult.type = "IC";
				} else if (len == 32 || scanData.indexOf('-') != -1) {
					this.scanResult.type = "QrCode";
				} else {
					this.scanResult.type = "ERR";
				}
				this.scanResult.code = scanData;
				console.log('keydownReceive获取结果:', scanData, this.scanResult.type, uniqueScanData);
				// 使用防抖方法发送结果
				this.debounceEmit(() => {
					this.$emit('getCode', {
						type: this.scanResult.type,
						code: uniqueScanData
					})
				})
			},
			KeydownReceive(e) {
				// 新增：阻止键盘事件冒泡和默认行为

				// 隐藏可能弹出的软键盘
				uni.hideKeyboard();

				// console.log("keyCode",e.keyCode);
				if (e.keyCode != 66) {
					this.keyCodes.push(e.keyCode);
					this.scanDate = Date.now();
				} else {
					console.log("ScanCodeCallback", "error");
					this.ScanCodeCallback();
				}
			},
			addScanCodeEvent() {
				// 确保之前的事件监听器已经移除
				this.removeScanCodeEvent();
								
				this.getValueTimeoutId = setInterval(() => {
					if (this.scanDate > 0 && Date.now() - this.scanDate > 200)
						this.ScanCodeCallback();
				}, 200);
				plus.key.addEventListener('keydown', this.KeydownReceive, false);
				console.log('添加键盘事件监听器');
			},
			removeScanCodeEvent() {
				if (this.getValueTimeoutId) {
					clearInterval(this.getValueTimeoutId);
					this.getValueTimeoutId = null;
				}
				plus.key.removeEventListener('keydown', this.KeydownReceive);
				console.log('移除键盘事件监听器');
			}
		}
	}
</script>

<style>
	/* 	.content{
		display: flex;
		flex-direction: column;
		align-items: center;
		justify-content: center;
		height: 100vh;
	} */
</style>